package demo.controller;

import cn.hutool.core.bean.BeanUtil;
import demo.Result;
import demo.dto.RequestAllocateDutyDto;
import demo.dto.RequestRemoveEmployeeDto;
import demo.entity.Seek;
import demo.entity.User;
import demo.entity.UserCompany;
import demo.service.*;
import org.apache.shiro.authz.annotation.RequiresAuthentication;
import org.apache.shiro.authz.annotation.RequiresRoles;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.validation.annotation.Validated;
import org.springframework.web.bind.annotation.PostMapping;
import org.springframework.web.bind.annotation.RequestBody;
import org.springframework.web.bind.annotation.RestController;

/**
 * @author 肖溥博文
 * @version 1.4
 */
@RestController
public class PositionController {
    @Autowired
    UserService userService;
    @Autowired
    CompanyService companyService;
    @Autowired
    UserCompanyService userCompanyService;
    @Autowired
    DepartmentService departmentService;
    @Autowired
    SeekService seekService;

    /**
     * 按 userCompany 对象判断工号是否分配
     *
     * @param
     * @return
     */
    @PostMapping("/isWorkIdExist")
    @RequiresAuthentication
    @RequiresRoles("HR")
    public Result isWorkIdExist(@RequestBody UserCompany userCompany) {
        if (userCompanyService.isWorkIdExist(userCompany).getCode() == 400)
            return Result.error("工号已分配");
        else
            return Result.success("工号未分配");
    }

    /**
     * 按 userCompany 在注册时对象判断工号是否分配
     *
     * @param
     * @return
     */
    @PostMapping("/isWorkIdExistWhenRecruit")
    @RequiresAuthentication
    @RequiresRoles("HR")
    public Result isWorkIdExistWhenRecruit(@RequestBody UserCompany userCompany) {
        if (userCompanyService.isWorkIdExistWhenRecruit(userCompany.getWorkId(), userCompany.getCompanyId()).getCode() == 400)
            return Result.error("工号已分配");
        else
            return Result.success("工号未分配");
    }

    /**
     * 给员工分配职位
     * 当添加新员工时，需要输入新员工的邀请码
     *
     * @param requestAllocateDutyDto 必须传入用户 id、工号、公司 id、部门 id 和职位。
     *                        <br /> 当添加新员工时，必须输入新员工的邀请码。
     * @return
     */
    @PostMapping("/allocDuty")
    @RequiresAuthentication
    @RequiresRoles("HR")
    public Result allocDuty(@Validated @RequestBody RequestAllocateDutyDto requestAllocateDutyDto) {
        UserCompany userCompany = new UserCompany();
        BeanUtil.copyProperties(requestAllocateDutyDto, userCompany);

        if (requestAllocateDutyDto.getInvitingCode() != null) {
            String invitingCode = requestAllocateDutyDto.getInvitingCode();
            Result findSeekResult = seekService.findByInvitingCode(invitingCode);
            if (findSeekResult.getCode() != 200) {
                return Result.error("添加用户失败，邀请码错误");
            }

            Seek seek = (Seek) findSeekResult.getData();
            if (!seek.getUid().equals(requestAllocateDutyDto.getUid())) {
                return Result.error("添加用户失败，邀请码错误");
            }
            if (!seek.getCompanyId().equals(requestAllocateDutyDto.getCompanyId())) {
                return Result.error("添加用户失败，邀请码错误");
            }

            seek.setValid(false);

            Result updateResult = userCompanyService.update(userCompany, true);
            if (updateResult.getCode() == 200) {
                seekService.update(seek);
            }
            return updateResult;
        }

        return userCompanyService.update(userCompany, false);
    }

    /**
     * 移除员工
     *
     * @param requestRemoveEmployeeDto 必须包含用户 id，可以包含离职原因
     * @return 结果对象
     */
    @PostMapping("/removeEmployee")
    @RequiresAuthentication
    @RequiresRoles("HR")
    public Result removeEmployee(@RequestBody RequestRemoveEmployeeDto requestRemoveEmployeeDto) {
        User userFound = userService.findUserByUid(requestRemoveEmployeeDto.getUid());
        if (userFound == null) {
            return Result.error("员工不存在，无法删除员工");
        }

        return userCompanyService.deleteEmployee(requestRemoveEmployeeDto.getUid(), requestRemoveEmployeeDto.getReason());
    }
}
